open feed file with close-on-exec bit set
authorJoey Hess <joeyh@joeyh.name>
Fri, 5 Sep 2025 20:02:17 +0000 (16:02 -0400)
committerJoey Hess <joeyh@joeyh.name>
Fri, 5 Sep 2025 20:02:17 +0000 (16:02 -0400)
parseFeedFromFile does not set the bit, so open and read the file
ourselves.

Versioned dependency on utf8-string should not cause any issues,
that version is available in all all versions of debian that package it.

Sponsored-by: the NIH-funded NICEMAN (ReproNim TR&D3) project
Command/ImportFeed.hs
doc/bugs/35_failed_tests_on_beegfs/comment_8_853bf59715ac755d046b54b282eaac7c._comment
git-annex.cabal

index 7b66a2b5077613b7e33dc8597a8272e7fdea7102..e36e72370204ece44a05bfae5954272a46f34f5c 100644 (file)
@@ -1,6 +1,6 @@
 {- git-annex command
  -
- - Copyright 2013-2024 Joey Hess <id@joeyh.name>
+ - Copyright 2013-2025 Joey Hess <id@joeyh.name>
  -
  - Licensed under the GNU AGPL version 3 or higher.
  -}
@@ -22,6 +22,7 @@ import Data.Time.Format
 import Data.Time.Calendar
 import Data.Time.LocalTime
 import Control.Concurrent.STM
+import Codec.Binary.UTF8.String (decodeString)
 import qualified Data.Text as T
 import qualified Data.Text.Encoding as TE
 import qualified Data.ByteString as B
@@ -48,6 +49,7 @@ import Logs.MetaData
 import Annex.MetaData
 import Annex.FileMatcher
 import Annex.UntrustedFilePath
+import qualified Utility.FileIO as F
 import qualified Utility.RawFilePath as R
 import qualified Database.ImportFeed as Db
 
@@ -158,19 +160,16 @@ getFeed o url st =
                | otherwise = get
 
        get = withTmpFile (literalOsPath "feed") $ \tmpf h -> do
-               let tmpf' = fromRawFilePath $ fromOsPath tmpf
                liftIO $ hClose h
-               ifM (downloadFeed url tmpf')
-                       ( parse tmpf'
+               ifM (downloadFeed url tmpf)
+                       ( parse tmpf
                        , do
                                recordfail
                                next $ feedProblem url
                                        "downloading the feed failed"
                        )
 
-       -- Use parseFeedFromFile rather than reading the file
-       -- ourselves because it goes out of its way to handle encodings.
-       parse tmpf = liftIO (parseFeedFromFile tmpf) >>= \case
+       parse tmpf = liftIO (parseFeedFromFile' tmpf) >>= \case
                Nothing -> debugfeedcontent tmpf "parsing the feed failed"
                Just f -> do
                        case decodeBS $ fromFeedText $ getFeedTitle f of
@@ -183,7 +182,7 @@ getFeed o url st =
                                        next $ return True
        
        debugfeedcontent tmpf msg = do
-               feedcontent <- liftIO $ readFileString (toOsPath tmpf)
+               feedcontent <- liftIO $ readFileString tmpf
                fastDebug "Command.ImportFeed" $ unlines
                        [ "start of feed content"
                        , feedcontent
@@ -265,11 +264,11 @@ findDownloads u f = catMaybes $ map mk (feedItems f)
                }
 
 {- Feeds change, so a feed download cannot be resumed. -}
-downloadFeed :: URLString -> FilePath -> Annex Bool
+downloadFeed :: URLString -> OsPath -> Annex Bool
 downloadFeed url f
        | Url.parseURIRelaxed url == Nothing = giveup "invalid feed url"
        | otherwise = Url.withUrlOptions Nothing $
-               Url.download nullMeterUpdate Nothing url (toOsPath f)
+               Url.download nullMeterUpdate Nothing url f
 
 startDownload :: AddUnlockedMatcher -> ImportFeedOptions -> Cache -> TMVar Bool -> ToDownload -> CommandStart
 startDownload addunlockedmatcher opts cache cv todownload = case location todownload of
@@ -645,3 +644,11 @@ feedState url = fromRepo $ gitAnnexFeedState $ fromUrl url Nothing False
  -}
 fromFeedText :: T.Text -> B.ByteString
 fromFeedText = TE.encodeUtf8
+
+{- Like Test.Feed.parseFeedFromFile, but ensures the close-on-exec bit is
+ - set when opening the file. -}
+parseFeedFromFile' :: OsPath -> IO (Maybe Feed)
+parseFeedFromFile' fp = parseFeedString <$> utf8readfile fp
+  where
+       utf8readfile :: OsPath -> IO String
+       utf8readfile f = fmap decodeString (hGetContents =<< F.openBinaryFile f ReadMode)
index 8b8010e8c45f289023af0c587af54f0778578cf2..997300e64e630b761250ec54519b5f1e7b513545 100644 (file)
@@ -21,7 +21,8 @@ Most dependencies of git-annex clearly don't open files there, and most open no
 files at all. Ones I need to check:
 
 * persistent-sqlite
-* feed (parseFeedFromFile)
+* feed (parseFeedFromFile uses openBinaryFile, updated git-annex to open
+  the file itself instead)
 * concurrent-output (addOutputBuffer uses openTempFile; emitOutputBuffer uses T.readFile)
-* magic
+* magic (update: checked it, it sets close-on-exec)
 """]]
index 8591e54d9fb65ce20cd5ba3e643eecf41ff84090..af69ee14dc204849d0a713198cb6d6c162171fa6 100644 (file)
@@ -206,7 +206,7 @@ custom-setup
     time (>= 1.9.1),
     directory (>= 1.2.7.0),
     async,
-    utf8-string,
+    utf8-string (>= 1.0.0),
     Cabal (< 4.0)
 
 Executable git-annex
@@ -234,7 +234,7 @@ Executable git-annex
    IfElse,
    monad-logger (>= 0.3.10),
    free,
-   utf8-string,
+   utf8-string (>= 1.0.0),
    bytestring,
    text,
    sandi,